package com.wdy.filter;

import com.wdy.entities.SecurityUser;
import com.wdy.ssafe.TokenManager;
import java.io.IOException;
import java.util.List;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.web.authentication.www.BasicAuthenticationFilter;

public class TokenAuthFilter extends BasicAuthenticationFilter {
  private TokenManager tokenManager;
  private RedisTemplate<String, Object> redisTemplate;

  public TokenAuthFilter(
      AuthenticationManager authenticationManager, TokenManager tokenManager, RedisTemplate<String, Object> redisTemplate) {
    super(authenticationManager);
    this.tokenManager = tokenManager;
    this.redisTemplate = redisTemplate;
  }

  @Override
  protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response,
      FilterChain chain) throws IOException, ServletException {
    UsernamePasswordAuthenticationToken authenticationToken = getAuthentication(request);
    if(null != authenticationToken){
      SecurityContextHolder.getContext().setAuthentication(authenticationToken);
    }
    chain.doFilter(request, response);
  }

  private UsernamePasswordAuthenticationToken getAuthentication(HttpServletRequest request) {
    String token = request.getHeader("token");
    if (null != token) {
      String username = tokenManager.parseToken(token);
      Object objPermissions = redisTemplate.opsForValue().get(username);
      if (null == objPermissions) {
        return null;
      }

      List<String> roles = (List<String>) objPermissions;
      SecurityUser securityUser = new SecurityUser();
      securityUser.setPermissionValueList(roles);
      return new UsernamePasswordAuthenticationToken(username, token,
          securityUser.getAuthorities());
    }
    return null;
  }
}
